package com.github.cosycode.imgtool.ctrl;

import com.github.cosycode.common.util.common.StrUtils;
import com.github.cosycode.common.util.io.IoUtils;
import com.github.cosycode.ext.se.util.FileUtils;
import com.github.cosycode.imgtool.rule.CheckConfig;
import com.github.cosycode.imgtool.rule.FileExistCheckBRO;
import com.github.cosycode.imgtool.tool.RegexUtils;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
import lombok.NonNull;
import org.apache.commons.lang3.StringUtils;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.nio.charset.Charset;
import java.nio.file.Files;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.function.Consumer;
import java.util.function.Function;

/**
 * <b>Description : </b>
 * <p>
 * <b>created in </b> 2022/8/7
 * </p>
 *
 * @author pengfchen
 * @since 1.0
 **/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class MarkdownFileProcessor {

    public static void findMdImgLink(@NonNull File markdownFile, CheckConfig config, Consumer<FileExistCheckBRO> consumer) throws IOException {
        if (config.isRelatePathEnable()) {
            config.setRelatePathEnable(markdownFile.getParent());
        }
        // 分析文件编码
        final String encodeType = FileUtils.analysisTextFileEncode(markdownFile);
        final Charset charset = Charset.forName(encodeType);
        // 读取文件
        try (final FileInputStream inputStream = new FileInputStream(markdownFile)) {
            final String content = IoUtils.readStringFromInputStream(inputStream, charset);
            // 将其中的 http 路径中的文件下载下来, 并放到本地路径, 并替换 URL
            StrUtils.findAll(RegexUtils.MARKDOWN_IMG_REGEX_DIRECTOR, content, path -> {
                FileExistCheckBRO rst = FileExistCheckBRO.analyze(path, config);
                if (rst == null) {
                    return;
                }
                consumer.accept(rst);
            });
        }
    }

    public static String replaceMdImgLink(@NonNull File markdownFile, CheckConfig config, Function<FileExistCheckBRO, String> function, boolean dryRun) throws IOException {
        if (config.isRelatePathEnable()) {
            config.setRelatePathEnable(markdownFile.getParent());
        }
        AtomicBoolean changeFlag = new AtomicBoolean(false);
        // 分析文件编码
        final String encodeType = FileUtils.analysisTextFileEncode(markdownFile);
        final Charset charset = Charset.forName(encodeType);
        // 读取文件
        final String fileContext;
        try (final FileInputStream inputStream = new FileInputStream(markdownFile)) {
            fileContext = IoUtils.readStringFromInputStream(inputStream, charset);
        }
        String newContext = StrUtils.replaceAll(RegexUtils.MARKDOWN_IMG_REGEX_DIRECTOR, fileContext, path -> {
            FileExistCheckBRO rst = FileExistCheckBRO.analyze(path, config);
            if (rst == null) {
                return path;
            }
            String apply = function.apply(rst);
            if (StringUtils.isBlank(apply)) {
                return path;
            }
            changeFlag.set(true);
            return apply;
        });
        if (!dryRun && changeFlag.get()) {
            // 保存文件内容
            try (OutputStream outputStream = Files.newOutputStream(markdownFile.toPath())) {
                IoUtils.writeStringToOutputStream(outputStream, newContext, charset);
            }
        }
        return newContext;
    }

}
